/**
 * 
 */
package de.cbf.cam.map2d.map;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.List;

import org.eclipse.swt.SWT;
import org.eclipse.swt.events.MouseEvent;
import org.eclipse.swt.events.MouseListener;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.widgets.Canvas;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Display;

import de.cbf.cam.map2d.listeners.GridPaintListener;
import de.cbf.cam.map2d.listeners.ObjectPaintListener;
import de.cbf.cam.map2d.shapes.Shape;

/**
 * @author Stefan Alter
 *
 */
public class Map extends Canvas {
	private ObjectPaintListener objectPainter;
	private boolean grid = false;
	private float zoomFactor = 1.0f;
	
	private Point mousePosition;
	
	private List<ActionListener> mouseDownListeners = new ArrayList<ActionListener>();
	private List<ActionListener> mouseDoubleClickListeners = new ArrayList<ActionListener>();
	private List<ActionListener> mouseUpListeners = new ArrayList<ActionListener>();
	/**
	 * @param parent
	 * @param style
	 */
	public Map(Composite parent, int style) {
		super(parent, style|SWT.H_SCROLL|SWT.V_SCROLL|SWT.DOUBLE_BUFFERED);
		setBackground(Display.getCurrent().getSystemColor(SWT.COLOR_WHITE));
		
		//paint grid
		if(grid){
			addPaintListener(new GridPaintListener(zoomFactor));
		}		
		objectPainter = new ObjectPaintListener(zoomFactor);		
		addPaintListener(objectPainter);
		
		addMouseListener(new MouseListenerMap());		
	}
	
	public void addObjectToMap(Shape shape){
		objectPainter.addObject(shape);		
	}
	
	public void removeObjectFromMap(Shape shape){
		objectPainter.removeObject(shape);		
	}
	
	/**
	 * @author Stefan Alter
	 *
	 */
	public class MouseListenerMap implements MouseListener {
		@Override
		public void mouseDoubleClick(MouseEvent e) {
			mousePosition=new Point(e.x,e.y);
			ActionEvent event = new ActionEvent(Map.this, ActionEvent.ACTION_PERFORMED, "mapMouseDoubleClick");
			for (ActionListener listener : mouseDoubleClickListeners) {
				listener.actionPerformed(event);
			}
		}
		@Override
		public void mouseDown(MouseEvent e) {
			Point point = new Point(e.x,e.y);
			mousePosition=point;
			ActionEvent event = new ActionEvent(Map.this, ActionEvent.ACTION_PERFORMED, "mapMouseDown");
			for (ActionListener listener : mouseDownListeners) {
				listener.actionPerformed(event);
			}
		}

		@Override
		public void mouseUp(MouseEvent e) {
			mousePosition=new Point(e.x,e.y);
			ActionEvent event = new ActionEvent(Map.this, ActionEvent.ACTION_PERFORMED, "mapMouseUp");
			for (ActionListener listener : mouseUpListeners) {
				listener.actionPerformed(event);
			}
		}
	}

	public Point getMousePosition() {
		return mousePosition;
	}

	public void setMousePosition(Point mousePosition) {
		this.mousePosition = mousePosition;
	}
	
//	============================
//		listener registry
//	============================
	public boolean registerMouseDownListener(ActionListener listener){
		return mouseDownListeners.add(listener);
	}
	public boolean registerMouseDoubleClickListener(ActionListener listener){
		return mouseDoubleClickListeners.add(listener);
	}
	public boolean registerMouseUpListener(ActionListener listener){
		return mouseUpListeners.add(listener);
	}
	public boolean removeMouseDownListener(ActionListener listener){
		return mouseDownListeners.remove(listener);
	}	
	public boolean removeMouseDoubleClickListener(ActionListener listener){
		return mouseDoubleClickListeners.remove(listener);
	}	
	public boolean removeMouseUPListener(ActionListener listener){
		return mouseUpListeners.remove(listener);
	}	
}
